// CallsTable.cpp : CallsTable is used to keep track of all the calls made in each procedures.
// Author: Achyut P Balaji
//

#include"CallsTable.h"

CallsTable::CallsTable() {
}

CallsTable* CallsTable::obj = NULL;


CallsTable* CallsTable::getInstance(){
	if(!obj) 
		obj = new CallsTable;
	return obj;
}

BOOLEAN CallsTable::insertCall(PROC_INDEX p1, PROC_INDEX p2) {
	if(callsList.at(p1).at(0) == -1) {
		callsList.at(p1).pop_back();
		callsList.at(p1).push_back(p2);
		return true;
	}
	bool temp = true;
	for(int i=0;i < callsList.at(p1).size();i++) {
		if(callsList.at(p1).at(i) == p2) 
			temp = false;
	}
	if (temp == true)
		callsList.at(p1).push_back(p2);
	return true;
}

void CallsTable::initialise(int size) {
	vector<PROC_INDEX> temp;
	temp.push_back(-1);
	for(int i=0;i<size;i++) {
		callsList.push_back(temp);
	}
}

BOOLEAN CallsTable::isCalled(PROC_INDEX p1, PROC_INDEX p2) {
	for(int i =0;i<callsList.at(p1).size();i++) {
		if(callsList.at(p1).at(i) == p2)
			return true;
	}
	return false;
}

PROC_LIST CallsTable::getProcCalled(PROC_INDEX p) {
	if(p<callsList.size()) {
		return callsList.at(p);
	}
	else {
		vector<PROC_INDEX> temp;
		temp.push_back(-1);
		return temp;
	}
}

PROC_LIST CallsTable::getList(PROC_INDEX p) {

	if(p<=callsList.size()){
		vector<PROC_INDEX> temp;
		int j=0;
		temp.push_back(p);
		if(callsList.at(p).at(0) == -1) {
			return temp;
		}
		while(j<temp.size()){
			if(callsList.at(temp.at(j)).at(0) != -1) {
				for(int i=0;i<callsList.at(temp.at(j)).size();i++) {
					bool bool1 = false;
					for(int k=0;k<temp.size();k++) {
						if(callsList.at(temp.at(j)).at(i) == temp.at(k)) {
							bool1 = true;
						}
					}
					if(bool1 == false) {
						temp.push_back(callsList.at(temp.at(j)).at(i));
					}
				}
			}
			j++;
		}

		return temp;
	}
	else {
		vector<PROC_INDEX> temp;
		temp.push_back(-1);
		return temp;
	}
}

PROC_LIST CallsTable::getProcList(PROC_INDEX p) {

	if(p<=callsList.size()){
		vector<PROC_INDEX> temp;
		int j=0;
		//temp.push_back(p);
		if(callsList.at(p).at(0) == -1) {
			return temp;
		}
		bool tempo = true;
		while(j<temp.size() || tempo==true){
			if(tempo==true){
				for(int i=0;i<callsList.at(p).size();i++) {
					bool bool1 = false;
					for(int k=0;k<temp.size();k++) {
						if(callsList.at(p).at(i) == temp.at(k)) {
							bool1 = true;
						}
					}
					if(bool1 == false) {
						temp.push_back(callsList.at(p).at(i));
					}
				}
				tempo = false;
			}
			else{
				if(callsList.at(temp.at(j)).at(0) != -1) {
					for(int i=0;i<callsList.at(temp.at(j)).size();i++) {
						bool bool1 = false;
						for(int k=0;k<temp.size();k++) {
							if(callsList.at(temp.at(j)).at(i) == temp.at(k)) {
								bool1 = true;
							}
						}
						if(bool1 == false) {
							temp.push_back(callsList.at(temp.at(j)).at(i));
						}
					}
				}
				j++;
			}
		}

		return temp;
	}
	else {
		vector<PROC_INDEX> temp;
		temp.push_back(-1);
		return temp;
	}
}